package com.such.kit.image;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Toolkit;
import java.awt.geom.AffineTransform;
import java.awt.image.AffineTransformOp;
import java.awt.image.BufferedImage;
import java.awt.image.CropImageFilter;
import java.awt.image.FilteredImageSource;
import java.awt.image.ImageFilter;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;

import com.such.kit.file.FileCommons;
import com.such.kit.validate.ValidateCommons;

/**
 * @作者 SUCH
 * @日期 2017-3-1 上午10:51:15
 * @描述 图片缩放工具类
 */
public class ImageZoom {

	private String enlargeName;
	private boolean usePrefix;
	private String prefixName;
	private boolean useSuffix;
	private String suffixName;

	/**
	 * <p>方法名：setEnlargeName</p>
	 * <p>描述：设置扩展名，默认使用原扩展名</p>
	 * @param enlargeName 扩展名
	 */
	public void setEnlargeName(String enlargeName) {
		this.enlargeName = enlargeName;
	}

	/**
	 * <p>方法名：usePrefix</p>
	 * <p>描述：为图片设置前缀</p>
	 * @param fixName 缀名
	 */
	public void usePrefix(String fixName) {
		if (ValidateCommons.isNotEmpty(fixName)) {
			this.usePrefix = true;
			this.prefixName = fixName;
		}
	}

	/**
	 * <p>方法名：useSuffix</p>
	 * <p>描述：为图片设置后缀</p>
	 * @param fixName 缀名
	 */
	public void useSuffix(String fixName) {
		if (ValidateCommons.isNotEmpty(fixName)) {
			this.useSuffix = true;
			this.suffixName = fixName;
		}
	}

	/**
	 * <p>方法名：zoomPadding</p>
	 * <p>描述：对图片放缩</p>
	 * @param imagePath 图片路径
	 * @param width 宽度 
     * @param height 高度
	 * @param isAutoPadding 比例失调是否需要补白
	 * @throws IOException
	 */
	public void zoomPadding(String imagePath, int width, int height, boolean isAutoPadding) 
			throws IOException {
		try {
			double ratio = 0.0;
			File imageFile = new File(imagePath);
			BufferedImage bufImage = ImageIO.read(imageFile);
			Integer bufWidth = bufImage.getWidth();
			Integer bufHeight = bufImage.getHeight();
			if (width != 0 && height != 0) {
				if (bufWidth > bufHeight) {
					ratio = Double.valueOf(width) / bufWidth;
				} else {
					ratio = Double.valueOf(height) / bufHeight;
				}
			}
			AffineTransform at = AffineTransform.getScaleInstance(ratio, ratio);
			AffineTransformOp atOp = new AffineTransformOp(at, AffineTransformOp.TYPE_NEAREST_NEIGHBOR);
			bufImage = atOp.filter(bufImage, null);
			if (isAutoPadding) {
				bufWidth = bufImage.getWidth();
				bufHeight = bufImage.getHeight();
				BufferedImage tempBufImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);  
				Graphics2D g2D = tempBufImage.createGraphics();
				g2D.setColor(Color.white);
				g2D.fillRect(0, 0, width, height);
				if (width == bufWidth) {
					g2D.drawImage(bufImage, 0, (height - bufHeight) / 2, bufWidth, bufHeight, Color.white, null);
				} else {
					g2D.drawImage(bufImage, (width - bufWidth) / 2, 0, bufWidth, bufHeight, Color.white, null);
				}
				g2D.dispose();
				bufImage = tempBufImage;
			}
			String enlargeName = FileCommons.getEnlargeName(imagePath);
			if (ValidateCommons.isNotEmpty(this.enlargeName)) {
				enlargeName = this.enlargeName;
			}
			if (this.usePrefix) {
				imagePath = FileCommons.addPerfix(imagePath, this.prefixName);
				imageFile = new File(imagePath);
			}
			if (this.useSuffix) {
				imagePath = FileCommons.addSuffix(imagePath, this.suffixName);
				imageFile = new File(imagePath);
			}
			ImageIO.write(bufImage, enlargeName, imageFile);
		} catch (IOException e) {
			throw e;
		}
	}

	/**
	 * <p>方法名：zoomCutting</p>
	 * <p>描述：对图片放缩</p>
	 * @param imagePath 图片路径
	 * @param width 宽度
	 * @param height 高度
	 * @param isAutoCutting 比例失调是否需要切割
	 * @throws IOException
	 */
	public void zoomCutting(String imagePath, int width, int height, boolean isAutoCutting) 
			throws IOException {
		try {
			double ratio = 0.0;
			File imageFile = new File(imagePath);
			BufferedImage bufImage = ImageIO.read(imageFile);
			Integer bufWidth = bufImage.getWidth();
			Integer bufHeight = bufImage.getHeight();
			if (width != 0 && height != 0) {
				double widthRatio = Double.valueOf(width) / bufWidth;
				double heightRatio = Double.valueOf(height) / bufHeight;
				if (widthRatio > heightRatio) {
					ratio = widthRatio;
				} else {
					ratio = heightRatio;
				}
			}
			AffineTransform at = AffineTransform.getScaleInstance(ratio, ratio);
			AffineTransformOp atOp = new AffineTransformOp(at, AffineTransformOp.TYPE_NEAREST_NEIGHBOR);
			bufImage = atOp.filter(bufImage, null);
			if (isAutoCutting) {
				bufWidth = bufImage.getWidth();
				bufHeight = bufImage.getHeight();
				int x = 0;
				int y = 0 ;
				if (width == bufWidth) {
					if (height > bufHeight) {
						y = (height - bufHeight) / 2;
					} else {
						y = (bufHeight - height) / 2;
					}
				} else {
					if (width > bufWidth) {
						x = (width - bufWidth) / 2;
					} else if (width < bufWidth) {
						x = (bufWidth - width) / 2;
					}
				}
				Image image = bufImage.getScaledInstance(bufWidth, bufHeight, Image.SCALE_DEFAULT);
				ImageFilter cropFilter = new CropImageFilter(x, y, width, height);
				image = Toolkit.getDefaultToolkit().createImage(new FilteredImageSource(bufImage.getSource(), cropFilter));
				BufferedImage tempBufImage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
				Graphics g = tempBufImage.getGraphics();
				g.drawImage(image, 0, 0, Color.white, null);
				g.dispose();
				bufImage = tempBufImage;
			}
			String enlargeName = FileCommons.getEnlargeName(imagePath);
			if (ValidateCommons.isNotEmpty(this.enlargeName)) {
				enlargeName = this.enlargeName;
			}
			if (this.usePrefix) {
				imagePath = FileCommons.addPerfix(imagePath, this.prefixName);
				imageFile = new File(imagePath);
			}
			if (this.useSuffix) {
				imagePath = FileCommons.addSuffix(imagePath, this.suffixName);
				imageFile = new File(imagePath);
			}
			ImageIO.write(bufImage, enlargeName, imageFile);
		} catch (IOException e) {
			throw e;
		}
	}

}
